#include <windows.h>
#include <iostream>
#include <SDL/SDL_image.h>
#include <SDL/SDL_ttf.h>
#include "Gomoku.h"
#include "MainWindow.h"
#include "PushButton.h"
#include "ButtonManager.h"
#include "PlayerTurnPrompter.h"
#include "GameScreen.h"
#include "Gomoku.h"
#include "Board.h"
#include "SelectScreen.h"
#include "GameScreen.h"

GameScreen::GameScreen()
: IScreen(), m_lastColor(COLOR_NONE), m_board(16, 16), m_isBlocked(false)
, m_currentInfos(INFOS_WAITING)
{
	Gomoku::Instance().CurrentPlayer = &Gomoku::Instance().getPlayers()[COLOR_BLACK];
	Gomoku::Instance().Board.init();
}

GameScreen::~GameScreen()
{
	ButtonManager::Instance().clearButtons();
	Gomoku::Instance().Threads->reinitThreads();
	Gomoku::Instance().reset();
}

void GameScreen::init()
{
	m_background.Surface = IMG_Load("images\\GameBackground.png");
	SDL_Color black = {0, 0, 0};
	m_currentPlayer.Surface = TTF_RenderText_Blended(MainWindow::Font(), "Current player: ", black);
	m_currentPlayer.Position.x = 32;
	m_currentPlayer.Position.y = 640;
	
	m_textInfos.Surface = TTF_RenderText_Solid(MainWindow::Font(), "Infos :", black);
	m_textInfos.Position.x = 220;
	m_textInfos.Position.y = 640;

	m_infos[INFOS_RULE_THREE].Surface = TTF_RenderText_Solid(MainWindow::Font(), "Error: Can't play here because of rule 3", black);
	m_infos[INFOS_AI].Surface = TTF_RenderText_Solid(MainWindow::Font(), "A.I is thinkiing...", black);
	m_infos[INFOS_WAITING].Surface = TTF_RenderText_Solid(MainWindow::Font(), "Waiting for player to play...", black);

	for (int i = 0; i < INFOS_COUNT; i++)
	{
		m_infos[i].Position.x = 280;
		m_infos[i].Position.y = 640;
	}

	ButtonManager::Instance().clearButtons();
	
	m_buttonReset = new PushButton(this, "Reset");
	m_buttonReset->setPosition(656, 16);
	m_buttonReset->CallBack = &On_buttonReset_Pressed;
	ButtonManager::Instance().addButton(m_buttonReset);

	m_buttonQuit = new PushButton(this, "Quit");
	m_buttonQuit->setPosition(656, 112);
	m_buttonQuit->CallBack = &On_buttonQuit_Pressed;
	ButtonManager::Instance().addButton(m_buttonQuit);

	m_buttonBack = new PushButton(this, "Back");
	m_buttonBack->setPosition(656, 64);
	m_buttonBack->CallBack = &On_buttonBack_Pressed;
	ButtonManager::Instance().addButton(m_buttonBack);

	m_buttonPrintBoard = new PushButton(this, "Print");
	m_buttonPrintBoard->setPosition(656, 160);
	m_buttonPrintBoard->CallBack = &On_buttonPrintBoard_Pressed;
#ifdef _DEBUG
	ButtonManager::Instance().addButton(m_buttonPrintBoard);
#endif

	m_checkBoxMovePieces = new CheckBox(this, "Can move pieces");
	m_checkBoxMovePieces->setPosition(640, 200);
	m_checkBoxMovePieces->CallBack = &On_checkBoxMovePieces_Checked;
	ButtonManager::Instance().addButton(m_checkBoxMovePieces);

	m_checkBoxRuleThree = new CheckBox(this, "Use rule three");
	m_checkBoxRuleThree->setPosition(640, 230);
	m_checkBoxRuleThree->CallBack = &On_checkBoxRuleThree_Checked;
	m_checkBoxRuleThree->CurrentState = CheckBox::ButtonState::PRESSED;
	m_checkBoxRuleThree->updateState();
	ButtonManager::Instance().addButton(m_checkBoxRuleThree);

	//m_checkBoxCanRemovePiece
	m_checkBoxCanRemovePiece = new CheckBox(this, "Can delete piece");
	m_checkBoxCanRemovePiece->setPosition(640, 260);
	m_checkBoxCanRemovePiece->CallBack = &On_checkBoxCanRemovePiece_Checked;
	m_checkBoxCanRemovePiece->CurrentState = CheckBox::ButtonState::PRESSED;
	m_checkBoxCanRemovePiece->updateState();
	ButtonManager::Instance().addButton(m_checkBoxCanRemovePiece);

	m_cursor.Surface = IMG_Load("images\\SelectedCaseCursor.png");
	m_cursor.setTransparence();

	m_capturedPieces[COLOR_BLACK].Surface = IMG_Load("images\\CapturedPieces_black.png");
	m_capturedPieces[COLOR_BLACK].setTransparence();
	m_capturedPieces[COLOR_BLACK].Position.x = 656;
	m_capturedPieces[COLOR_BLACK].Position.y = 528;
	m_capturedPieces[COLOR_WHITE].Surface = IMG_Load("images\\CapturedPieces_white.png");
	m_capturedPieces[COLOR_WHITE].setTransparence();
	m_capturedPieces[COLOR_WHITE].Position.x = 656;
	m_capturedPieces[COLOR_WHITE].Position.y = m_capturedPieces[COLOR_BLACK].Position.y + m_capturedPieces[COLOR_BLACK].Surface->h + 24;
	m_capturedPieceRects[COLOR_BLACK].x = 0;
	m_capturedPieceRects[COLOR_BLACK].y = 0;
	m_capturedPieceRects[COLOR_BLACK].w = 0;
	m_capturedPieceRects[COLOR_BLACK].h = m_capturedPieces[COLOR_BLACK].Surface->h;
	m_capturedPieceRects[COLOR_WHITE].x = 0;
	m_capturedPieceRects[COLOR_WHITE].y = 0;
	m_capturedPieceRects[COLOR_WHITE].w = 0;
	m_capturedPieceRects[COLOR_WHITE].h = m_capturedPieces[COLOR_BLACK].Surface->h;
}

bool GameScreen::draw()
{
	SDL_Surface* screen = MainWindow::Screen();

	SDL_BlitSurface(m_background.Surface, NULL, screen, &m_background.Position);
	m_board.draw();
	if (PlayerTurnPrompter::Instance().Count != 0)
	{
		PlayerTurnPrompter::Instance().prompt(screen);
		PlayerTurnPrompter::Instance().decreaseCount();
	}
	ButtonManager::Instance().draw(screen);
	SDL_BlitSurface(m_currentPlayer.Surface, NULL, screen, &m_currentPlayer.Position);
	SDL_Rect pos;
	Image* piece = m_board.getPiece((unsigned char)Gomoku::Instance().CurrentPlayer->Color);
	pos.x = m_currentPlayer.Position.x + 4 + m_currentPlayer.Surface->w;
	pos.y = m_currentPlayer.Position.y + m_currentPlayer.Surface->h / 2 - piece->Surface->h / 2;

	if (m_currentInfos != INFOS_NONE)
	{
		SDL_BlitSurface(m_textInfos.Surface, NULL, screen, &m_textInfos.Position);
		SDL_BlitSurface(m_infos[m_currentInfos].Surface, NULL, screen, &m_infos[m_currentInfos].Position);
	}
	SDL_BlitSurface(piece->Surface, NULL, screen, &pos);
	SDL_BlitSurface(m_cursor.Surface, NULL, screen, &m_cursor.Position);

	m_capturedPieceRects[COLOR_BLACK].w = (Gomoku::Instance().getPlayers()[COLOR_WHITE].EnnemyPiecesCount / 2) * 24;
	m_capturedPieceRects[COLOR_WHITE].w = (Gomoku::Instance().getPlayers()[COLOR_BLACK].EnnemyPiecesCount / 2) * 24;

	SDL_BlitSurface(m_capturedPieces[0].Surface, &m_capturedPieceRects[0], screen, &m_capturedPieces[0].Position);
	SDL_BlitSurface(m_capturedPieces[1].Surface, &m_capturedPieceRects[1], screen, &m_capturedPieces[1].Position);
	return (true);
}

void GameScreen::doEvents()
{
	/*if (Gomoku::Instance().CurrentPlayer->Winner == true && PlayerTurnPrompter::Instance().Count == 0)
	{
		PlayerTurnPrompter::Instance().setText(Gomoku::Instance().CurrentPlayer->Name + " WIN!!!!");
		PlayerTurnPrompter::Instance().Count = 100;
	}
	if (Gomoku::Instance().CurrentPlayer->Color != m_lastColor)
	{
		PlayerTurnPrompter::Instance().setText(Gomoku::Instance().CurrentPlayer->Name + "'s turn!");
		PlayerTurnPrompter::Instance().Count = 45;
		m_lastColor = Gomoku::Instance().CurrentPlayer->Color;
	}*/
	for (int i = 0; i < 2; i++)
	{
		if (Gomoku::Instance().getPlayers()[i].Winner == true && PlayerTurnPrompter::Instance().Count == 0)
		{
			PlayerTurnPrompter::Instance().setText(Gomoku::Instance().getPlayers()[i].Name + " WIN!!!!", Gomoku::Instance().getPlayers()[i].Color);
			PlayerTurnPrompter::Instance().Count = 100;
			break ;
		}
	}
	if (Gomoku::Instance().CurrentPlayer->Color != m_lastColor)
	{
		PlayerTurnPrompter::Instance().setText(Gomoku::Instance().CurrentPlayer->Name + "'s turn!", Gomoku::Instance().CurrentPlayer->Color);
		PlayerTurnPrompter::Instance().Count = 45;
		m_lastColor = (unsigned char)Gomoku::Instance().CurrentPlayer->Color;
	}

	SDL_Event& e = MainWindow::Event();

	if (e.type == SDL_QUIT)
		MainWindow::Close(true);

	if (e.type == SDL_MOUSEMOTION)
	{
		int x = 0, y = 0;
		SDL_GetMouseState(&x, &y);
		bool cond_x = (x >= 16 && x <= 16 + m_board.getBackground()->w);
		bool cond_y = (y >= 16 && y <= 16 + m_board.getBackground()->h);
		if (cond_x && cond_y)
		{
			x = (x - 16) / 32;
			y = (y - 16) / 32;
			if (x >= Board::WIDTH)
				x = (int)Board::WIDTH - 1;
			if (y >= Board::HEIGHT)
				y = (int)Board::HEIGHT - 1;
			x = x * 32 + 16;
			y = y * 32 + 16;
			m_cursor.Position.x = x;
			m_cursor.Position.y = y;
			SDL_ShowCursor(0);
		}
		else
			SDL_ShowCursor(1);
	}
}

void GameScreen::setBlockOnButtons(bool _blocked)
{
	m_isBlocked = _blocked;
}

bool GameScreen::isBlocked() const
{
	return (m_isBlocked);
}

bool On_buttonReset_Pressed(IScreen* _screen)
{
	GameScreen* mps = dynamic_cast<GameScreen*>(_screen);
	Gomoku::Instance().reset();
	mps->m_lastColor = COLOR_NONE;
	PlayerTurnPrompter::Instance().setText("Game reinitialized", COLOR_BLACK);
	PlayerTurnPrompter::Instance().Count = 50;
	return (true);
}

bool On_buttonQuit_Pressed(IScreen*)
{
	MainWindow::Close(true);
	return (false);
}

bool On_buttonBack_Pressed(IScreen* _screen)
{
	MainWindow::SelectScreen(new SelectScreen);
	return (false);
}

bool On_buttonPrintBoard_Pressed(IScreen*)
{
#ifdef _DEBUG
	system("CLS");
	for (BoardCase y = 0; y < Board::HEIGHT; y++)
	{
		std::cout << y;
		if (y < 10)
			std::cout << " ";
		std::cout << ": ";
		for (BoardCase x = 0; x < Board::WIDTH; x++)
		{
			if (GET_COLOR(Gomoku::Instance().Board.Cases[y][x]) != COLOR_NONE)
				std::cout << GET_COLOR(Gomoku::Instance().Board.Cases[y][x]) << " ";
			else
				std::cout << "- ";
		}
		std::cout << std::endl;
	}
#endif
	return (true);
}

 bool On_checkBoxMovePieces_Checked(IScreen* _screen)
{
	GameScreen* screen = dynamic_cast<GameScreen*>(_screen);
	if (screen->isBlocked() == true)
		return (false);
	return (true);
}

 bool On_checkBoxRuleThree_Checked(IScreen* _screen)
{
	GameScreen* screen = dynamic_cast<GameScreen*>(_screen);
	if (screen->isBlocked() == false)
		Gomoku::Instance().RuleThreeUse = !Gomoku::Instance().RuleThreeUse;
	else
		return (false);
	 return (true);
}

bool On_checkBoxCanRemovePiece_Checked(IScreen* _screen)
{
	GameScreen* screen = dynamic_cast<GameScreen*>(_screen);
	if (screen->isBlocked() == true)
		return (false);
	return (true);
}
